#ifndef __TPilaPoro__
#define __TPilaPoro__

#include<iostream>
using namespace std;

#include"tvectorporo.h"
#include"tporo.h"

/** \file  tpilaporo.h
 *  \brief Esta es una clase basada en la propiedades y operaciones posibles con una pila de numeros complejos.
 *
 * Autor: Óscar Toledo Ballester, 48666364c.
 *      Autor: Alejandro Serrano Cases, 74364527f
 *
 *    Con esta clase podemos trabajar con un gran número de operaciones posibles con una pila, con la particularidad de que nuestra pila sera de
 *      numeros complejos. Está implementada mediante composicion de una lista de números complejos.
 */

class TPilaPoro
{
   /** \brief Operador << de TPilaPoro.
    *  Mostramos la Pila con el siguiente formato".
    *  \param os Ostream que recojerá la pila con el formato para mostrar.
    *  \param tpp TPilaPoro que queremos mostrar.
    *  \return Nos devuelve un ostream que recoje la Pila en el formato adecuado.
         */
   friend ostream& operator<<(ostream& os,const TPilaPoro& tpp);


   public:
      /** \brief Constructor por defecto de la clase.
       *  No hace nada.
       */
      TPilaPoro();
      /** \brief Constructor de copia de la clase.
       *  Generamos una Pila exactamente igual a la pasada como parámetro.
       *  \param tpp TPilaPoro que servira para generar la copia.
       */
      TPilaPoro(const TPilaPoro &tpp);
      /** \brief Destructor de la clase.
       *  No hace nada.
       */
      ~TPilaPoro();
      /** \brief Operador de asignación de la clase.
       *  Copiamos exactamente la Pila pasada como parámetro.
       *  \param tpp TPilaPoro que servira para copiar en el otro TPilaPoro.
       *  \return Nos devuelve el TPilaPoro que llama al metodo modificado para ser igual que el parametro.
       */
      TPilaPoro& operator=(const TPilaPoro& tpp);
      /** \brief Operador de comparacion de TPilaPoro.
       *  Compararemos toda la pila.
       *  \param tpp TPilaPoro que compararemos con el que efectua la llamada.
       *  \return Nos devuelve un booleano que segun si es cierta la comparacion devolverá true y en caso contrario false.
       */
      bool operator==(const TPilaPoro& tpp);
      /** \brief Operador de no igualdad de TPilaPoro.
       *  Compararemos toda la pila.
       *  \param tpp TPilaPoro que compararemos con el que efectua la llamada.
       *  \return Nos devuelve un booleano que segun si es cierta la comparacion devolverá false y en caso contrario true.
       */
      bool operator!=(const TPilaPoro& tpp);
      /** \brief Método EsVacia.
       *  Comprobamos si la pila tiene algun elemento.
       *  \return Nos devuelve un booleano que en caso de que sea vacia tendra como valor true y en caso contrario su valor sera false.
       */
      bool EsVacia() const;
      /** \brief Metodo Apilar.
       *  Apilamos el elemento pasado como parametro.
       *  \param c Complejo que apilaremos.
       *  \return Nos devuelve un booleano que segun si es cierta la operación devolverá false y en caso contrario true.
       */
      bool Apilar(const TPoro& p);
      /** \brief Metodo Desapilar.
       *  Desapilamos el elemento que está en la cima de la pila.
       *  \return Nos devuelve un booleano que segun si es cierta la operación devolverá false y en caso contrario true.
       */
      void Desapilar();
      /** \brief Metodo Cima.
       *  Buscamos el primer elemento de la pila.
       *  \return Nos devuelve un complejo con el primer elemento de la pila.
       */
      TPoro Cima() const;
      /** \brief Metodo Longitud.
       *  Medimos el tamaño de la pila.
       *  \return Nos devuelve un entero con el tamaño de la pila.
       */
      int Longitud() const;
      /** \brief Operador resta de TPilaPoro.
       *  Creamos una pila nueva que contendrá todos los elementos de la primera que la segunda pila no contiene.
       *  \param tpp Segundo operando de la resta.
       *  \return Nos devuelve una pila de complejos nueva que contiene los elementos en el mismo orden de la primera que no contiene la
       *  segunda.
       */
      TPilaPoro operator+(const TPilaPoro& tpp) const;

   private:
      /** \brief Declaracion de la variable de tipo TVectorPoro.
       * Este será el vector por el que esté compuesta la pila.
       */
      TVectorPoro v;
      /** \brief Declaracion de la variable de tipo int.
       * Este será el numero que nos indique la proxima posicion vacia.
       */
      int posicion;
      /** \brief Declaracion de la variable de tipo TPoro.
       * Este será el TPoro que se devolverá en caso de acceder a una posicion erronea.
       */
      TPoro error;

};
#endif

